package com.kdgc.energy.dmm.delete;

import com.kdgc.energy.dmm.Environment;
import com.kdgc.energy.dmm.condition.Condition;
import com.kdgc.energy.dmm.time.TimeStatistical;
import org.apache.metamodel.UpdateSummary;
import org.apache.metamodel.delete.RowDeletionBuilder;
import org.apache.metamodel.jdbc.JdbcDataContext;
import org.apache.metamodel.query.FilterItem;
import org.apache.metamodel.schema.MutableTable;

import java.util.ArrayList;
import java.util.List;

/**
 * 删除
 *
 * @author xu.wenchang
 * @version 1.0 2022/04/19
 */
public class Delete {
    private Class<?> clazz;
    
    private List<FilterItem> filterItems;
    
    private TimeStatistical timeStatistical;
    
    public Delete(Class<?> clazz) {
        this.clazz = clazz;
        this.filterItems = new ArrayList<>();
        this.timeStatistical = new TimeStatistical();
        this.timeStatistical.phaseStart("build");
    }
    
    public Delete where(Condition condition) {
        this.filterItems.add(condition.getDelegate());
        return this;
    }
    
    public int execute() {
        JdbcDataContext dataContext = new JdbcDataContext(Environment.getDataSource());
        UpdateSummary summary = dataContext.executeUpdate(updateCallback -> {
            MutableTable table = Environment.get(Delete.this.clazz)
                                            .getTable();
            RowDeletionBuilder delete = updateCallback.deleteFrom(table);
            for (FilterItem fi : Delete.this.filterItems) {
                delete.where(fi);
            }
            Delete.this.timeStatistical.phaseEnd("build");
            Delete.this.timeStatistical.phaseStart("execute");
            
            String sql = delete.toSql();
            Delete.this.timeStatistical.setName(sql);
            
            if (Environment.isShowSQL()) {
                Environment.getWriter()
                           .write(sql);
            }
            
            delete.execute();
            Delete.this.timeStatistical.phaseEnd("execute");
        });
        
        this.timeStatistical.end();
        
        if (Environment.isStatExecTime()) {
            Environment.getWriter()
                       .write(this.timeStatistical.statisticalInfo());
        }
        
        return summary.getDeletedRows()
                      .orElse(0);
    }
}
